<?php

namespace common\modules\user\controllers\backend;

use backend\components\AdminModule as Module;
use backend\components\RbacPhpManager;
use common\modules\user\models\backend\RoleForm;
use common\modules\user\models\backend\RoleSearch;
use common\components\AdminController;
use Yii;
use yii\filters\VerbFilter;
use yii\helpers\ArrayHelper;
use yii\web\HttpException;
use yii\web\Response;

/**
 * Roles controller.
 */
class RoleController extends AdminController
{

    /**
     * {@inheritdoc}
     */
    public function behaviors()
    {
        $behaviors = [];

        $behaviors['verbs'] = [
            'class'   => VerbFilter::className(),
            'actions' => [
                'index'        => ['get'],
                'create'       => ['get', 'post'],
                'update'       => ['get', 'put', 'post'],
                'delete'       => ['post', 'delete'],
                'batch-delete' => ['post', 'delete'],
            ],
        ];

        return $behaviors;
    }

    /**
     * Roles list page.
     */
    public function actionIndex()
    {
        $searchModel = new RoleSearch;
        $dataProvider = $searchModel->search(Yii::$app->request->get());

        $page = $this->createGridViewPage($dataProvider, $searchModel);
        return $page->render();
    }

    /**
     * Create role page.
     */
    public function actionCreate()
    {
        $model = new RoleForm(['scenario' => RoleForm::SCENARIO_CREATE]);
        $roleArray = ArrayHelper::map($model->roles, 'name', 'name');
        $ruleArray = ArrayHelper::map($model->rules, 'name', 'name');
        $permissionArray = ArrayHelper::map($model->permissions, 'name', 'name');

        if ($model->load(Yii::$app->request->post()))
        {
            /** @var RbacPhpManager $auth */
            $auth = Yii::$app->authManager;
            $auth->setCustomEditMode();

            if ($model->validate())
            {
                if ($model->add())
                {
                    return $this->redirect(['update', 'name' => $model->name]);
                }
                else
                {
                    Yii::$app->session->setFlash('danger', Module::t('user', 'BACKEND_ROLES_FLASH_FAIL_ADMIN_CREATE'));
                }
            }
            elseif (Yii::$app->request->isAjax)
            {
                Yii::$app->response->format = Response::FORMAT_JSON;
                return $model->getErrors();
            }
        }

        return $this->render('create', [
            'model'           => $model,
            'roleArray'       => $roleArray,
            'ruleArray'       => $ruleArray,
            'permissionArray' => $permissionArray,
        ]);
    }

    /**
     * Update role page.
     *
     * @param string $name Role name
     *
     * @return mixed
     */
    public function actionUpdate($name)
    {
        /** @var RoleForm $model */
        $model = RoleForm::findIdentity($name);
        $model->setScenario(RoleForm::SCENARIO_UPDATE);

        if ($model->load(Yii::$app->request->post()))
        {
            /** @var RbacPhpManager $auth */
            $auth = Yii::$app->authManager;
            $auth->setCustomEditMode();

            if ($model->validate())
            {
                if ($model->update())
                {
                    return $this->refresh();
                }
                else
                {
                    Yii::$app->session->setFlash('danger', Module::t('user', 'BACKEND_ROLES_FLASH_FAIL_ADMIN_UPDATE'));
                }
            }
            elseif (Yii::$app->request->isAjax)
            {
                Yii::$app->response->format = Response::FORMAT_JSON;
                return $model->getErrors();
            }
        }

        $page = $this->createFormViewPage(
            $model,
            RoleForm::SCENARIO_UPDATE,
            [
                'pageTitle' => Yii::t('backend/user', 'Update Role'),
            ]
        );
        return $page->render();
    }

    /**
     * Delete role page.
     *
     * @param string $name Role name
     *
     * @return mixed
     */
    public function actionDelete($name)
    {
        $model = $this->findRole($name);

        /** @var RbacPhpManager $auth */
        $auth = Yii::$app->authManager;
        $auth->setCustomEditMode();

        if ( ! Yii::$app->authManager->remove($model))
        {
            Yii::$app->session->setFlash('danger', Module::t('user', 'BACKEND_ROLES_FLASH_FAIL_ADMIN_DELETE'));
        }

        return $this->redirect(['index']);
    }

    /**
     * Find role by name.
     *
     * @param string $name Role name
     *
     * @return \yii\rbac\Role Role
     *
     * @throws HttpException 404 error if role not found
     */
    protected function findRole($name)
    {
        if (($model = Yii::$app->authManager->getRole($name)) !== null)
        {
            return $model;
        }
        else
        {
            throw new HttpException(404, Module::t('user', 'BACKEND_ROLES_NOT_FOUND'));
        }
    }
}
